package com.yc.bigdata.hbase.core;

import org.apache.hadoop.hbase.client.Mutation;
import org.apache.hadoop.hbase.client.Result;
import org.apache.hadoop.hbase.client.ResultScanner;
import org.apache.hadoop.hbase.client.Scan;
import org.apache.hadoop.hbase.filter.FilterList;

import java.io.*;
import java.util.List;
import java.util.Map;

/**
 * <p></p>
 *
 * @author: YuanChilde
 * @date: 2020-01-16 14:02
 * @version: 1.0
 * Modification History:
 * Date    Author      Version     Description
 * -----------------------------------------------------------------
 * 2020-01-16 14:02    YuanChilde     1.0        新增
 */
public interface HBaseOperations {
    /**
     * Executes the given action against the specified table handling resource management.
     * <p>
     * Application exceptions thrown by the action object get propagated to the caller (can only be unchecked).
     * Allows for returning a result object (typically a domain object or collection of domain objects).
     *
     * @param tableName the target table
     * @param <T> action type
     * @return the result object of the callback action, or null
     */
    <T> T execute(String tableName, TableCallback<T> mapper);

    /**
     * Scans the target table, using the given column family.
     * The content is processed row by row by the given action, returning a list of domain objects.
     *
     * @param tableName target table
     * @param family column family
     * @param <T> action type
     * @return a list of objects mapping the scanned rows
     */
    <T> List<T> find(String tableName, String family, final RowMapper<T> mapper);

    /**
     * Scans the target table, using the given column family.
     * The content is processed row by row by the given action, returning a list of domain objects.
     *
     * @param tableName target table
     * @param family column family
     * @param qualifier column qualifier
     * @param <T> action type
     * @return a list of objects mapping the scanned rows
     */
    <T> List<T> find(String tableName, String family, String qualifier, final RowMapper<T> mapper);

    /**
     * Scans the target table using the given {@link Scan} object. Suitable for maximum control over the scanning
     * process.
     * The content is processed row by row by the given action, returning a list of domain objects.
     *
     * @param tableName target table
     * @param scan table scanner
     * @param <T> action type
     * @return a list of objects mapping the scanned rows
     */
    <T> List<T> find(String tableName, final Scan scan, final RowMapper<T> mapper);

    /**
     * Gets an individual row from the given table. The content is mapped by the given action.
     *
     * @param tableName target table
     * @param rowName row name
     * @param mapper row mapper
     * @param <T> mapper type
     * @return object mapping the target row
     */
    <T> T get(String tableName, String rowName, final RowMapper<T> mapper);

    /**
     * Gets an individual row from the given table. The content is mapped by the given action.
     *
     * @param tableName target table
     * @param rowName row name
     * @param familyName column family
     * @param mapper row mapper
     * @param <T> mapper type
     * @return object mapping the target row
     */
    <T> T get(String tableName, String rowName, String familyName, final RowMapper<T> mapper);

    /**
     * Gets an individual row from the given table. The content is mapped by the given action.
     *
     * @param tableName target table
     * @param rowName row name
     * @param familyName family
     * @param qualifier column qualifier
     * @param mapper row mapper
     * @param <T> mapper type
     * @return object mapping the target row
     */
    <T> T get(String tableName, final String rowName, final String familyName, final String qualifier, final RowMapper<T> mapper);

    /**
     * 执行put update or delete
     * @param tableName
     * @param action
     */
    void execute(String tableName, MutatorCallback action);

    /**
     *
     * @param tableName
     * @param mutation
     */
    void saveOrUpdate(String tableName, Mutation mutation);

    /**
     *
     * @param tableName
     * @param mutations
     */
    void saveOrUpdates(String tableName, List<Mutation> mutations);


    /**
     * 插入/更新记录（单行单列族-单列单值）
     *
     * @param tableName         表名
     * @param rowKey               行名
     * @param columnFamily      列族名
     * @param column            列名
     * @param value             值
     */
    void putData(String tableName, String rowKey, String columnFamily, String column, String value);

    /**
     * 批量插入/更新记录（单行单列族-多列多值）
     * @param tableName
     * @param rowKey
     * @param tableName
     * @param columnFamily
     * @param columns
     * @param values
     */
    void putDatas(String tableName, String rowKey, String columnFamily, String[] columns, String[] values);

    /**
     * 查找一行记录
     *
     * @param tableName         表名
     * @param rowKey            行名
     */
    Map<String, String> selectRow(String tableName, String rowKey);

    /**
     * 查找单行单列族单列记录
     *
     * @param tableName         表名
     * @param rowKey            行名
     * @param columnFamily      列族名
     * @param column            列名
     * @return
     */
    String selectValue(String tableName, String rowKey, String columnFamily, String column);
    /**
     * 通过过滤器来查询数据
     * @param tableName
     * @param rowKey
     * @param filterList
     * @return Result
     */
    Result getRow(String tableName, String rowKey, FilterList filterList);
    /**
     * 批量检索数据.
     *
     * @param tableName 表名
     * @param startRowKey 起始RowKey
     * @param endRowKey 终止RowKey
     * @return ResultScanner实例
     */
    ResultScanner getScanner(String tableName, String startRowKey, String endRowKey);
    /**
     * 批量检索数据.
     *
     * @param tableName 表名
     * @param startRowKey 起始RowKey
     * @param endRowKey 终止RowKey
     * @param filterList 过滤条件
     * @return ResultScanner实例
     */
    ResultScanner getScanner(String tableName, String startRowKey, String endRowKey, FilterList filterList);
    /**
     * 查询表中所有行（Scan方式）
     *
     * @param tableName
     * @return
     */
    Map<String, Map<String, String>> scanAllRecord(String tableName) throws IOException;
    /**
     * 创建表
     * create <table>, {NAME => <column family>, VERSIONS => <VERSIONS>}
     * shell command: create ‘user’, ‘cf1’
     *
     * @param tableName
     * @param columnFamily
     * @throws IOException
     */
    void createTable(String tableName, List<String> columnFamily) throws IOException;

    /**
     * 创建或重写表
     * @param tableName
     * @param columnFamily
     * @throws IOException
     */
    void createOrOverwriteTable(String tableName, List<String> columnFamily) throws IOException;

    /**
     * 增加列簇
     * @param tableName
     * @param columnFamily
     * @throws IOException
     */
    void addColumnFamily(String tableName, String columnFamily) throws IOException;
    /**
     * 查询库中所有表的表名
     * @return
     */
    List<String> getAllTableNames() throws IOException;

    /**
     * 删除一行记录
     *
     * @param tablename         表名
     * @param rowkey            行名
     */
    void deleteRow(String tablename, String rowkey) throws IOException;
    /**
     * 删除单行单列簇单列记录
     *
     * @param tablename         表名
     * @param rowkey            行名
     * @param columnFamily      列簇名
     * @param column            列名
     */
    void deleteColumn(String tablename, String rowkey, String columnFamily, String column) throws IOException;
    /**
     * 删除单行单列簇记录
     * @param tablename         表名
     * @param rowkey            行名
     * @param columnFamily      列簇名
     */
    void deleteColumnFamily(String tablename, String rowkey, String columnFamily) throws IOException;
    /**
     * 删除表
     *
     * @param tableName
     * @throws IOException
     */
    void deleteTable(String tableName) throws IOException;
}
